#include <fstream>
#include "stream_puller.h"
#include "stream_pusher.h"
#include "osd_text.h"

using namespace stream;

int main(int argc, char** argv) {
  int ret = 0;
  LogInfo* log_ifo = new LogInfo(7, "./log", "log"); 

  StreamPullerInfo puller_ifo;
  // puller_ifo.streamAddress = "rtsp://192.168.0.64:554/media/video1";
  // puller_ifo.streamAddress = "rtsp://2.2.2.65:554/Streaming/Channels/101?transportmode=unicast&profile=Profile_1";
  puller_ifo.streamAddress = "rtsp://admin:atcctv@1100@2.2.2.65:554/ch01/main/av_stream";
  puller_ifo.transferType = "tcp";
  puller_ifo.enType = AV_CODEC_ID_H264;  //h264  MPP_VIDEO_CodingAVC
  puller_ifo.vdecChn = 0;
  std::cout<<"puller_ifo.enType:"<<puller_ifo.enType<<std::endl;
  CUStreamPuller *puller = new CUStreamPuller(nullptr, &puller_ifo, log_ifo);
  if (ret != (puller->init_params()) != 0) {
    spdlog::get("logger")->info("ERROR puller->init_params error ret:{}\n", ret);
    return ret;
  }
  std::thread(&CUStreamPuller::start_pull, puller).detach();

  stream::CVStreamOsdInfo osd_ifo;
  osd_ifo.dstWidth = 1920;
  osd_ifo.dstHeight = 1080;
  osd_ifo.boxThick = 3;
  osd_ifo.boxColorNG = cv::Scalar(0, 0, 255);
  osd_ifo.boxColorOK = cv::Scalar(0, 255, 0);
  osd_ifo.fontHeight = 30;                        

  stream::CVOsdText* osder = new stream::CVOsdText(&osd_ifo, log_ifo);
  if (ret != (osder->init_params()) != 0) {
    spdlog::get("logger")->info("ERROR pusher->init_params error ret:{}\n", ret);
    return ret;
  }


  StreamPusherInfo pusher_ifo;
  pusher_ifo.formatName = "flv";
  pusher_ifo.codecProfile = "main";
  pusher_ifo.fps = 25;
  pusher_ifo.bitrate = 4096;        // Mbps
  pusher_ifo.enType = AV_CODEC_ID_H264;   //MPP_VIDEO_CodingAVC
  pusher_ifo.vEncChn = 0;
  // pusher_ifo.streamAddress = "rtmp://192.168.0.10:9935/push/x3";
  pusher_ifo.streamAddress = "rtmp://2.2.2.110:9935/live/livestream";
  pusher_ifo.dstWidth = puller_ifo.oriWidth;
  pusher_ifo.dstHeight = puller_ifo.oriHeight;

  CUStreamPusher *pusher = new CUStreamPusher(&pusher_ifo, log_ifo);
  if (ret != (pusher->init_params()) != 0) {
    spdlog::get("logger")->info("ERROR pusher->init_params error ret:{}\n", ret);
    return ret;
  }
  std::thread(&CUStreamPusher::start_push, pusher).detach();


  int x = 100;
  int y = 100;
  int cnt = 0;
  stream::ImageBlob buffer(stream::ImageBlobMode_BGR);
  while(true) {
    std::this_thread::sleep_for(std::chrono::milliseconds(3));
    if (x >= puller_ifo.oriWidth) {x = 100;}
    if (y >= puller_ifo.oriHeight) {y = 100;}

    ret = puller->get_frame(buffer);
    if (ret != 0) { continue; }

    // std::cout << "bgr_img w:" << buffer.img.cols << " h:" << buffer.img.rows << " c:" << buffer.img.channels() << std::endl;
    // cv::rectangle(buffer.img, cv::Rect(x++,y++,200,200), cv::Scalar(255,0,0), 3);
    std::vector<stream::OSDDrawInfo> osdd_ifos;
    for(int i = 0; i < 9; i++) {
      stream::OSDDrawInfo osdd_ifo;
      // osdd_ifo.texts.push_back("O正确");
      osdd_ifo.texts.push_back("N错误");
      osdd_ifo.x = x + i*150;
      osdd_ifo.y = y;
      osdd_ifo.w = 100;
      osdd_ifo.h = 200;
      osdd_ifos.push_back(osdd_ifo);
    }
    x++;
    y++;
    ret = osder->draw_osd(buffer, osdd_ifos);

    if (cnt++ % 50 == 0) {
      std::string temp_path = std::to_string(cnt)+".png";
      imwrite(temp_path, buffer.img);
    }

    ret = pusher->add_frame(buffer); 

  }
  return 0;
}
